package com.jason.sms.agent.protocol.cmpp3.client;

import java.io.DataInputStream;
import java.io.DataOutputStream;
import java.net.Socket;
import java.util.LinkedList;
import java.util.concurrent.Callable;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.Future;
import java.util.logging.Level;
import java.util.logging.Logger;

import com.jason.sms.agent.protocol.cmpp3.component.SmsSendedManager;
import com.jason.sms.agent.protocol.cmpp3.msg.LoginMsg;
import com.jason.sms.agent.protocol.cmpp3.msg.LoginMsgResp;
import com.jason.sms.agent.protocol.cmpp3.msg.Msg;
import com.jason.sms.agent.protocol.cmpp3.msg.MsgCommand;
import com.jason.sms.agent.protocol.cmpp3.util.Utils;

public class CmppClient {
	
	private boolean isRunning = true;
	
	private Logger log = Logger.getLogger("CmppClient..");
	
	private LinkedList<Msg> sendList = new LinkedList<Msg>();
	
	private SmsSendedManager manager = SmsSendedManager.getManager();

	private Object lock = new Object();

	private ExecutorService executor;

	private Socket socket;

	private DataInputStream dis;

	private DataOutputStream dos;
	
	private boolean isLogin = false;
	
	private Writer writer;
	
	private Reader reader;

	public void start() {
		try {
			socket = new Socket(Configer.getIsmgIp(), Configer.getIsmgPort());
			dis = new DataInputStream(socket.getInputStream());
			dos = new DataOutputStream(socket.getOutputStream());
		} catch (Exception e) {
			log.log(Level.SEVERE, "连接IMSG时出现错误"+e.getMessage());
		}
		executor = Executors.newFixedThreadPool(5);
		writer = new Writer();
		reader = new Reader();
		executor.execute(writer);
		executor.execute(reader);
	}

	public void login() {
		LoginMsg lm = new LoginMsg();
		lm.setCommonId(MsgCommand.CMPP_CONNECT);
		lm.setTotalLength(12 + 6 + 16 + 1 + 4);
		lm.setSequenceId(Utils.getSeq());
		lm.setSourceAddr(Configer.getSpId());
		lm.setAuthenticatorSource(Utils.getLoginMd5(Configer.getSpId(),Configer.getSpPwd()));
		lm.setVersion((byte) 14);
		lm.setTimestamp(Integer.parseInt(Utils.getMMDDHHMMSS()));
		synchronized (lock) {
			if(socket != null && socket.isConnected()){
				sendList.addLast(lm);
				lock.notifyAll();
			}else{
				log.log(Level.WARNING,"未连接imsg!");
			}
		}
	}
	
	public void setIsLogin(boolean isLogin){
		log.info("登录状态="+isLogin);
		this.isLogin = isLogin;
	}
	
	class Writer implements Runnable{
		
		public void run(){
			while(isRunning){
				synchronized(lock){
					while(sendList.size()<=0){
						try{
							lock.wait();
						}catch(Exception e){
							e.printStackTrace();
						}
					}
					Msg msg = sendList.poll();
					byte[] pack = Utils.packMsg(msg);
					try {
						dos.write(pack);
						dos.flush();
					} catch (Exception e) {
						e.printStackTrace();
					}
					manager.addSendMsg(msg);
				}
			}
		}
	}
	
	class Reader implements Runnable{
		
		public void run(){
			while(isRunning){
				try {
					int len = dis.readInt();
					if ((len > 0) && (len < 500)) {
						byte[] data = new byte[len - 4];
						dis.readFully(data);
						Msg msg = Utils.parseMsg(data);
						process(msg);
					} else {
						
					}
				} catch (Exception ef) {
					ef.printStackTrace();
				}
			}
		}
		//返回消息的处理.
		public void process(Msg msg){
			if(msg.getCommonId() == MsgCommand.CMPP_CONNECT_RESP){
				LoginMsgResp loginResp = (LoginMsgResp)msg;
				if(loginResp.getStatus() == 0){
					CmppClient.this.setIsLogin(true);
				}
			}else{
				manager.getRecvMsg(msg);
			}
		}
	}

	

}
